/* Copyright © 2010 LPRM
Universidade Federal do Espírito Santo - RNP-GT CWTools

This file is part of GW-Android.

GW-Android is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

GW-Android is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with GW-Android. If not, see <http://www.gnu.org/licenses/>. */
package br.ufes.cwtools.android;

import java.io.InputStream;

import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

import android.util.Log;

public class GwApplicationParser {
	private GwApplicationParser() {
		/* Prevents instantiation. */
	}
	
	public static GwApplication parse(InputStream source) {
		try {
			SAXParser parser = SAXParserFactory.newInstance().newSAXParser();
			GwApplicationHandler handler = new GwApplicationHandler();
			parser.parse(source, handler);
			return handler.getApplication();
		} catch (Exception e) {
			e.printStackTrace();
			return null;
		} 
	}
}

class GwApplicationHandler extends DefaultHandler {
	private static final String TAG = "XmlParser";
	
	private static final String COMPONENT = "Component";
	private static final String ACTION = "Action";
	private static final String ACTION_COMPONENT = "ActionComponent";
	
	private GwApplication app = null;
	private Action currentAction = null;
	private String currentActionTag = null;
	
	public GwApplication getApplication() {
		return this.app;
	}
	
	@Override
	public void startDocument() throws SAXException {
		super.startDocument();
		this.app = new GwApplication();
	}
	
	@Override
	public void startElement(String uri, String localName, String qName,
			Attributes attributes) throws SAXException {
		super.startElement(uri, localName, qName, attributes);
		
		if (localName.equalsIgnoreCase(COMPONENT)) {
			String name = attributes.getValue("name");
			String className = attributes.getValue("class");
			String tag = attributes.getValue("tag");
			String pack = attributes.getValue("package");
			if (name != null && className != null && tag != null && pack != null) {
				this.app.putComponent(tag, new ComponentDefinition(name, className,pack));
			} else Log.d(TAG, "One or more attributes missing for element " + COMPONENT + ".");
		} else if (localName.equalsIgnoreCase(ACTION)) {
			String name = attributes.getValue("name");
			String tag = attributes.getValue("tag");
			if (name != null && tag != null) {
				this.currentAction = new Action(name);
				this.currentActionTag = tag;
			} else Log.d(TAG, "One or more attributes missing for element " + ACTION + ".");
		} else if (localName.equalsIgnoreCase(ACTION_COMPONENT) ) {
			if (this.currentAction != null) {
				String componentTag = attributes.getValue("component");
				if (componentTag != null) {
					ComponentDefinition component = this.app.getComponent(componentTag);
					if (component != null) {
						this.currentAction.addComponent(component);
					} else Log.d(TAG, "Component not found.");
				} else Log.d(TAG, "Attibute missing for element " + ACTION_COMPONENT + ".");
			} else Log.d(TAG, "Element " + ACTION_COMPONENT + " found outside an " + ACTION + ".");
		}
	}
	
	@Override
	public void endElement(String uri, String localName, String qName)
			throws SAXException {
		super.endElement(uri, localName, qName);
		
		if (localName.equalsIgnoreCase(ACTION)) {
			this.app.putAction(currentActionTag, currentAction);
			this.currentAction = null;
			this.currentActionTag = null;
		}
	}
}